N2O ePS + ePSproc preliminary multi-orb analysis: core 1s events (pt 2) Angle-resolved data

05/10/20

Paul Hockett

*** Preliminary results.

Background

Basic analysis of N2O ePolyScat results for core ionization events, O(1s) and N(1s). For backgound and methods, see ePSdata overview, ePSdata methods and ePS/ePSproc tutorial docs.

Pt 1: analysis of basic photoionization properties and matrix elements.

Pt 2: angle-resolved observables (this doc).

To do list:

  • Check electronic structure outputs vs. known thresholds. (From fig. 4 in the PRP it looks like the O(1s) results are shifted up by ~20eV, TBC.)
  • Analyse ePS computational precision (via gauge results).
  • Estimate accuracy of photoionization properties by comparison with experimental data. (Cf. recent XeF2 results - good, but required ~9eV energy shift, reasons TBC.)
  • Finish pt 2.

Setup

Env

In [1]:
!hostname
Stimpy
In [2]:
!conda env list
# conda environments:
#
                         C:\Program Files (x86)\Microsoft Visual Studio\Shared\Anaconda3_64
                         C:\Program Files (x86)\Microsoft Visual Studio\Shared\Anaconda3_64\envs\dataVis3D
                         C:\Program Files (x86)\Microsoft Visual Studio\Shared\Anaconda3_64\envs\dataVis3D-yt
                         C:\Program Files (x86)\Microsoft Visual Studio\Shared\Anaconda3_64\envs\ePSdev
                         C:\Program Files (x86)\Microsoft Visual Studio\Shared\Anaconda3_64\envs\ePSpkgTest2
                         C:\Program Files (x86)\Microsoft Visual Studio\Shared\Anaconda3_64\envs\fibre-sim
                         C:\Program Files (x86)\Microsoft Visual Studio\Shared\Anaconda3_64\envs\ipykernel_py2
                         C:\Program Files (x86)\Microsoft Visual Studio\Shared\Anaconda3_64\envs\pkgTest
                         C:\Program Files (x86)\Microsoft Visual Studio\Shared\Anaconda3_64\envs\pypi-test
                         C:\Program Files (x86)\Microsoft Visual Studio\Shared\Anaconda3_64\envs\seabreeze-bk
                         C:\Program Files (x86)\Microsoft Visual Studio\Shared\Anaconda3_64\envs\test
base                     C:\ProgramData\Anaconda3
ePSdev                   C:\Users\femtolab\.conda\envs\ePSdev
epsdev                *  C:\Users\femtolab\.conda\envs\epsdev
seabreeze                C:\Users\femtolab\AppData\Local\conda\conda\envs\seabreeze
tensorflow               C:\Users\femtolab\AppData\Local\conda\conda\envs\tensorflow

Load modules

In [3]:
import sys
import os
from pathlib import Path
import numpy as np
# import epsproc as ep
import xarray as xr

from datetime import datetime as dt
timeString = dt.now()
In [4]:
# For module testing, include path to module here, otherwise use global installation
if sys.platform == "win32":
    modPath = r'D:\code\github\ePSproc'  # Win test machine
    winFlag = True
else:
    modPath = r'/home/femtolab/github/ePSproc/'  # Linux test machine
    winFlag = False
    
sys.path.append(modPath)
import epsproc as ep
# # TODO: tidy this up!
# from epsproc.util import matEleSelector
# from epsproc.geomFunc import geomCalc, geomUtils
# from epsproc.geomFunc.lfblmGeom import lfblmXprod

# Plotters
from epsproc.plot import hvPlotters

# Multijob class dev code
from epsproc.classes.multiJob import ePSmultiJob
* pyevtk not found, VTK export not available. 
In [5]:
hvPlotters.setPlotters()
# import bokeh
# import holoviews as hv
# hv.extension('bokeh')

Load data

In [6]:
# # Scan for subdirs, based on existing routine in getFiles()
fileBase = r'D:\VMs\Share\ePSshare\N2O\N20_wf'  # Test dir on Stimpy (Win machine)
In [7]:
N2Odata = ePSmultiJob(fileBase, verbose = 0)
keys = [0,1,2]  # Set for 1s datasets only (ugly!)
N2Odata.scanFiles(keys = keys)
N2Odata.jobsSummary()
Found 3 directories, with 21 files.
Job structure: subDirs
(Results E stacked to one dataset per dir.)

*** Job dir 0 details
Directory: D:\VMs\Share\ePSshare\N2O\N20_wf\orb1_S
7 files
{   'batch': 'ePS N2O, batch N2O_wf, orbital orb1_S',
    'event': 'orb 1 ionization (O 1s, S/A1).',
    'orbE': -562.219888836424,
    'orbLabel': 'O 1s, S/A1'}

*** Job dir 1 details
Directory: D:\VMs\Share\ePSshare\N2O\N20_wf\orb2_S
7 files
{   'batch': 'ePS N2O, batch N2O_wf, orbital orb2_S',
    'event': 'orb 2 ionization (N 1s, S/A1).',
    'orbE': -431.308631832806,
    'orbLabel': 'N 1s, S/A1'}

*** Job dir 2 details
Directory: D:\VMs\Share\ePSshare\N2O\N20_wf\orb3_S
7 files
{   'batch': 'ePS N2O, batch N2O_wf, orbital orb3_S',
    'event': 'orb 3 ionization (N 1s, S/A1).',
    'orbE': -427.26774100883597,
    'orbLabel': 'N 1s, S/A1'}

System properties

Here orbitals 1,2,3 are all core 1s orbitals, centred on:

  1. O
  2. N (central)
  3. N (terminal)
In [8]:
N2Odata.molSummary()
*** Molecular structure
*** Molecular orbital list (from ePS output file)
EH = Energy (Hartrees), E = Energy (eV), NOrbGrp, OrbGrp, GrpDegen = degeneracies and corresponding orbital numbering by group in ePS, NormInt = single centre expansion convergence (should be ~1.0).
props Sym EH Occ E NOrbGrp OrbGrp GrpDegen NormInt
orb
1 S -20.6612 2.0 -562.219889 1.0 1.0 1.0 0.979634
2 S -15.8503 2.0 -431.308632 1.0 2.0 1.0 0.999998
3 S -15.7018 2.0 -427.267741 1.0 3.0 1.0 0.983661
4 S -1.6338 2.0 -44.457962 1.0 4.0 1.0 0.999465
5 S -1.4519 2.0 -39.508211 1.0 5.0 1.0 0.999243
6 S -0.8306 2.0 -22.601777 1.0 6.0 1.0 0.999545
7 P -0.7759 2.0 -21.113314 1.0 7.0 2.0 0.999991
8 P -0.7759 2.0 -21.113314 2.0 7.0 2.0 0.999991
9 S -0.6985 2.0 -19.007153 1.0 8.0 1.0 0.999692
10 P -0.4961 2.0 -13.499569 1.0 9.0 2.0 0.999984
11 P -0.4961 2.0 -13.499569 2.0 9.0 2.0 0.999984
*** Warning: some orbital convergences outside single-center expansion convergence tolerance (0.01):
[[1.         0.97963433]
 [3.         0.98366107]]
In [9]:
# Quick manual fix for orb/job labels

N2Odata.jobLabel(key=1, lString = "(central)")
N2Odata.jobLabel(key=2, lString = "(terminal)")

Molecular frame (MF) results

Making use of the raw matrix elements, the MFPADs can be plotted as a function of polarization geometry. Here are the results for a few energy slices, and each ionization channel, in polar and cart forms to give an overview.

The polarization geometries correspond to the laser field polarization aligned with the (x,y,z) molecular axes, as shown above. Note that the z-pol ('parallel') case is cylindrically symmetric, but not up-down symmetric. The (x,y) cases ('perpendicular') are not cylindrically symmetric.

NOTE: it seems like Plotly won't do more than ~12 subplots here, reasons TBD, so, for now, I've skipped the perpendicular N(1s) MFPADs here, since they show little energy dependence.

In [10]:
# Compute (numerical version without BLM computation)
N2Odata.mfpadNumeric()
In [11]:
# Set data ranges
Erange=[560, 620, 10]
Etype = 'Ehv'

O(1s) MF

In [12]:
# Set key for job
keys = 0
In [13]:
# MFPAD spherical polar plots with Plotly (interactive)
# Note x and y pol geoms are identical apart from rotation, so only x is plotted here.
N2Odata.mfpadPlot(Etype = Etype, Erange = Erange, selDims = {'Labels':['z','x']}, keys = keys, backend = 'pl')
Sph plots: O 1s, S/A1
Plotting with pl
Sph plots: O 1s, S/A1
Plotting with pl
In [14]:
# Gridded surface plots

N2Odata.mfpadPlot(Etype = Etype, Erange = Erange, pStyle='grid', keys = keys, backend = 'mpl')
Grid plot: O 1s, S/A1

N(1s) central MF

In [15]:
# Set key for job
keys = 1
In [16]:
# MFPAD spherical polar plots with Plotly (interactive)
# Note x and y pol geoms are identical apart from rotation, so only x is plotted here.
N2Odata.mfpadPlot(Etype = Etype, Erange = Erange, selDims = {'Labels':['z']}, keys = keys, backend = 'pl')
Sph plots: N 1s, S/A1 (central)
Plotting with pl
In [17]:
# Gridded surface plots

N2Odata.mfpadPlot(Etype = Etype, Erange = Erange, pStyle='grid', keys = keys, backend = 'mpl')
Grid plot: N 1s, S/A1 (central)

N(1s) terminal MF

In [18]:
# Set key for job
keys = 2
In [19]:
# MFPAD spherical polar plots with Plotly (interactive)
# Note x and y pol geoms are identical apart from rotation, so only x is plotted here.
N2Odata.mfpadPlot(Etype = Etype, Erange = Erange, selDims = {'Labels':['z']}, keys = keys, backend = 'pl')
Sph plots: N 1s, S/A1 (terminal)
Plotting with pl
In [20]:
# Gridded surface plots

N2Odata.mfpadPlot(Etype = 'Ehv', Erange = Erange, pStyle='grid', keys = keys, backend = 'mpl')
Grid plot: N 1s, S/A1 (terminal)

MF comparison plots

Angle-dependence vs. E plots. By dropping the (sort-of) redundant $\phi$ coord, one can generate $(E,\theta)$ maps which show the main trends. Here each channel is plotted for cross-section and phase.

In [21]:
selDims = {'Phi':0, 'Labels':['z','x']}
Erange = Erange[0:2]  # Reset for full resolution
In [22]:
keys = 0
N2Odata.mfpadPlot(Etype = 'Ehv', Erange = Erange, selDims = selDims, keys = keys, pType = 'a', pStyle='grid', backend = 'mpl')
N2Odata.mfpadPlot(Etype = 'Ehv', Erange = Erange, selDims = selDims, keys = keys, pType = 'phase', pStyle='grid', backend = 'mpl')
Grid plot: O 1s, S/A1
Grid plot: O 1s, S/A1
In [23]:
keys = 1
N2Odata.mfpadPlot(Etype = 'Ehv', Erange = Erange, selDims = selDims, keys = keys, pType = 'a', pStyle='grid', backend = 'mpl')
N2Odata.mfpadPlot(Etype = 'Ehv', Erange = Erange, selDims = selDims, keys = keys, pType = 'phase', pStyle='grid', backend = 'mpl')
Grid plot: N 1s, S/A1 (central)
Grid plot: N 1s, S/A1 (central)
In [24]:
keys = 2
N2Odata.mfpadPlot(Etype = 'Ehv', Erange = Erange, selDims = selDims, keys = keys, pType = 'a', pStyle='grid', backend = 'mpl')
N2Odata.mfpadPlot(Etype = 'Ehv', Erange = Erange, selDims = selDims, keys = keys, pType = 'phase', pStyle='grid', backend = 'mpl')
Grid plot: N 1s, S/A1 (terminal)
Grid plot: N 1s, S/A1 (terminal)

Versions

In [25]:
import scooby
scooby.Report(additional=['epsproc', 'xarray', 'jupyter'])
Out[25]:
Mon Oct 05 19:41:44 2020 Eastern Daylight Time
OS Windows CPU(s) 32 Machine AMD64
Architecture 64bit RAM 63.9 GB Environment Jupyter
Python 3.7.3 (default, Apr 24 2019, 15:29:51) [MSC v.1915 64 bit (AMD64)]
epsproc 1.3.0-dev xarray 0.15.0 jupyter Version unknown
numpy 1.19.2 scipy 1.3.0 IPython 7.12.0
matplotlib 3.3.1 scooby 0.5.6
Intel(R) Math Kernel Library Version 2020.0.0 Product Build 20191125 for Intel(R) 64 architecture applications